﻿using LxCore;

namespace LxCore
{
    public class SolveSetting : JsObject
    {
        public ConvectionSchemes EnergyConvScheme
        {
            get => _EnergyConvScheme;
            set { _EnergyConvScheme = value; RaisePropertyChanged(nameof(EnergyConvScheme)); }
        }
        private ConvectionSchemes _EnergyConvScheme = ConvectionSchemes.SecondOrder;
        public ParameterBase<double> EnergyRelaxFactor
        {
            get => _EnergyRelaxFactor;
            set { _EnergyRelaxFactor = value; RaisePropertyChanged(nameof(EnergyRelaxFactor)); }
        }
        private ParameterBase<double> _EnergyRelaxFactor = new ConstField.Double(0.99);
        public ConvectionSchemes TurbulenceConvScheme
        {
            get => _TurbulenceConvScheme;
            set { _TurbulenceConvScheme = value; RaisePropertyChanged(nameof(TurbulenceConvScheme)); }
        }
        private ConvectionSchemes _TurbulenceConvScheme = ConvectionSchemes.SecondOrder;
        public ParameterBase<double> TurblenceRelaxFactor
        {
            get => _TurblenceRelaxFactor;
            set { _TurblenceRelaxFactor = value; RaisePropertyChanged(nameof(TurblenceRelaxFactor)); }
        }
        private ParameterBase<double> _TurblenceRelaxFactor = new ConstField.Double(0.8);
        public ConvectionSchemes MomentumConvScheme
        {
            get => _MomentumConvScheme;
            set { _MomentumConvScheme = value; RaisePropertyChanged(nameof(MomentumConvScheme)); }
        }
        private ConvectionSchemes _MomentumConvScheme = ConvectionSchemes.SecondOrder;

        public ParameterBase<double> MomentumRelaxFactor
        {
            get => _MomentumRelaxFactor;
            set { _MomentumRelaxFactor = value; RaisePropertyChanged(nameof(MomentumRelaxFactor)); }
        }
        private ParameterBase<double> _MomentumRelaxFactor = new ConstField.Double(0.7);
        public ParameterBase<double> PressureRelaxFactor
        {
            get => _PressureRelaxFactor;
            set { _PressureRelaxFactor = value; RaisePropertyChanged(nameof(PressureRelaxFactor)); }
        }
        private ParameterBase<double> _PressureRelaxFactor = new ConstField.Double(0.3);
        public override void FromJsonKV(string key, IJsonReader jsReader)
        {
            switch (key)
            {
                case nameof(EnergyConvScheme): EnergyConvScheme = jsReader.ReadEnum<ConvectionSchemes>(); break;
                case nameof(EnergyRelaxFactor): jsReader.ReadObject(EnergyRelaxFactor, e => EnergyRelaxFactor = e); break;
                case nameof(MomentumConvScheme): MomentumConvScheme = jsReader.ReadEnum<ConvectionSchemes>(); break;
                case nameof(MomentumRelaxFactor): jsReader.ReadObject(MomentumRelaxFactor, e => MomentumRelaxFactor = e); break;
                case nameof(PressureRelaxFactor): jsReader.ReadObject(PressureRelaxFactor, e => PressureRelaxFactor = e); break;
                default: base.FromJsonKV(key, jsReader); break;
            }
        }
        public override void ToJsonKV(IJsonWriter jsWriter)
        {
            base.ToJsonKV(jsWriter);
            var pm = Parent as PhysicalModel;
            if(pm.IsEnergyEnabled)
            {
                if (pm.FlowType != null)
                {
                    jsWriter.WriteEnum(nameof(EnergyConvScheme), EnergyConvScheme);
                }
                jsWriter.WriteObject(nameof(EnergyRelaxFactor), EnergyRelaxFactor, true);
            }
            if (pm.FlowType != null)
            {
                jsWriter.WriteEnum(nameof(MomentumConvScheme), MomentumConvScheme);
                jsWriter.WriteObject(nameof(MomentumRelaxFactor), MomentumRelaxFactor, true);
                jsWriter.WriteObject(nameof(PressureRelaxFactor), PressureRelaxFactor, true);
            }
        }
    }
}
